#ifndef __FIFO_H__
#define __FIFO_H__

#ifdef __cplusplus
extern "C" {
#endif

#include <stdio.h>
#include <stdint.h>
#include "mutex.h"

#ifndef C_ARRAY_SIZE
#define C_ARRAY_SIZE(x)		(sizeof(x) / sizeof(x[0]))
#endif

#ifndef C_MIN
#define C_MIN(a, b)				((a) < (b) ? (a) : (b))
#endif

#ifndef C_MAX
#define C_MAX(a, b)				((a) > (b) ? (a) : (b))
#endif

typedef struct {
	uint8_t *buf;
	uint32_t in;
	uint32_t out;
	size_t size;
	c_mutex_t lock;
	char name[32];
} fifo_t;

typedef struct {
	int t;
	int l;
	char *v;
} tlv_t;

fifo_t *fifo_new(size_t nmemb, size_t size);

int fifo_in(fifo_t *fifo, const void *buf, size_t size, uint32_t tm);

int fifo_out(fifo_t *fifo, void *buf, size_t size, uint32_t tm);

void fifo_free(fifo_t *fifo);

int fifo_tlv_read(fifo_t *fifo, int *type, unsigned char *data, unsigned int *size);

int fifo_tlv_can_read(fifo_t *fifo, int *type);

int fifo_tlv_write(fifo_t *fifo, int type, unsigned char *data, unsigned int size);

int fifo_tlv_write_lock(fifo_t *fifo, int type, unsigned char *data, unsigned int size);

int fifo_tlv_can_read_len(fifo_t *fifo, int *type);

uint32_t fifo_space(fifo_t *fifo);

uint32_t fifo_cnt(fifo_t *fifo);

uint32_t fifo_put(fifo_t *fifo, const void *buf, uint32_t len);

uint32_t fifo_get(fifo_t *fifo, void *buf, uint32_t len);


#ifdef __cplusplus
}
#endif

#endif
